home *** CD-ROM | disk | FTP | other *** search
/ Games of Daze / Infomagic - Games of Daze (Summer 1995) (Disc 1 of 2).iso / x2ftp / msdos / libs / 3dvect39 / joystick.asm < prev    next >
Encoding:
Assembly Source File  |  1994-10-30  |  13.7 KB  |  440 lines

  1. ;░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░
  2. ;
  3. ; Filename     : joystick.asm
  4. ; Included from: Main Assembley Module
  5. ; Description  : Joystick routines
  6. ;
  7. ; Written by: John McCarthy
  8. ;             1316 Redwood Lane
  9. ;             Pickering, Ontario.
  10. ;             Canada, Earth, Milky Way (for those out-of-towners)
  11. ;             L1X 1C5
  12. ;
  13. ; Internet/Usenet:  BRIAN.MCCARTHY@CANREM.COM
  14. ;         Fidonet:  Brian McCarthy 1:229/15
  15. ;   RIME/Relaynet: ->CRS
  16. ;
  17. ; Home phone, (905) 831-1944, don't call at 2 am eh!
  18. ;
  19. ; Send me your protected mode source code!
  20. ; Send me your Objects!
  21. ; But most of all, Send me a postcard!!!!
  22. ;
  23. ;░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░
  24.  
  25.          .386p
  26.          jumps
  27.  
  28. code32   segment para public use32
  29.          assume cs:code32, ds:code32
  30.  
  31.          include pmode.ext                  ; protected mode externals by TRAN
  32.  
  33.          include macros.inc
  34.          include equ.inc
  35.  
  36.          public _joy_tax
  37.          public _joy_tay
  38.          public _joy_tbx
  39.          public _joy_tby
  40.          public _joy_lastcallstate
  41.          public _joy_thiscallstate
  42.  
  43.          public _joycenax
  44.          public _joycenay
  45.          public _joycenbx
  46.          public _joycenby
  47.          public _joy_ax
  48.          public _joy_ay
  49.          public _joy_bx
  50.          public _joy_by
  51.  
  52.          public _joy_deadzone
  53.  
  54.          public _joy_rawjoystick
  55.          public _joy_justgetbutton
  56.          public _joy_calibratejoystick
  57.          public _joy_waitalloff
  58.          public _joy_cartisianjoystick
  59.  
  60. ;░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░
  61. ;port 201h :
  62. ;
  63. ;  bit    JOYSTICK       PADDLE
  64. ;  ---    --------       ------
  65. ;  7      B  button 2    D button
  66. ;  6      B  button 1    C button
  67. ;  5      A  button 2    B button
  68. ;  4      A  button 1    A button
  69. ;  3      B  y-axis      D Coordinate
  70. ;  2      B  x-axis      C Coordinate
  71. ;  1      A  y-axis      B Coordinate
  72. ;  0      A  x-axis      A Coordinate
  73. ;░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░
  74.  
  75.          time_out equ 3000                  ; time out before abort
  76.          joyport equ 0201h                  ; joystick port address
  77.  
  78. _joy_tax dd 0                               ; joystick raw data
  79. _joy_tay dd 0
  80. _joy_tbx dd 0
  81. _joy_tby dd 0
  82. _joy_lastcallstate db 0                     ; last button state / button down      = 0f0h
  83. _joy_thiscallstate db 0                     ; this button state / button up states = 00fh
  84.  
  85. _joycenax dd 0                              ; center of joystick upon entry
  86. _joycenay dd 0
  87. _joycenbx dd 0
  88. _joycenby dd 0
  89. _joy_ax  dd 0                               ; cartisian joystick co-ordinates
  90. _joy_ay  dd 0
  91. _joy_bx  dd 0
  92. _joy_by  dd 0
  93.  
  94. _joy_deadzone dd 1000                       ; dead zone where centered joystick has no effect
  95.  
  96. ;░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░
  97. ; Rawjoystick: Get raw joystick data
  98. ; In: null
  99. ; Out:
  100. ;   EAX - x of joystick a
  101. ;   EBX - y of joystick a
  102. ;   ECX - x of joystick b
  103. ;   EDX - y of joystick b
  104. ; Notes:
  105. ; Machine dependant!
  106. ; Routine sets timers running and flags results as they come up.
  107. ; This way, all timers are checked at once.
  108. ;░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░
  109.  
  110. _joy_rawjoystick:
  111.          xor bl,bl                          ; reset attempt flag, when all ports come in, exit
  112.  
  113.          cmp _joy_tax,-1                    ; test if port operational
  114.          je raw_misxa
  115.          inc bl                             ; count number of ports waiting to come in
  116.          mov _joy_tax,0                     ; init values, -1 = port inactive
  117. raw_misxa:
  118.          cmp _joy_tay,-1
  119.          je raw_misya
  120.          inc bl
  121.          mov _joy_tay,0
  122. raw_misya:
  123.          cmp _joy_tbx,-1
  124.          je raw_misxb
  125.          inc bl
  126.          mov _joy_tbx,0
  127. raw_misxb:
  128.          cmp _joy_tby,-1
  129.          je raw_misyb
  130.          inc bl
  131.          mov _joy_tby,0
  132. raw_misyb:
  133.  
  134.          cli                                ; irq's off
  135.          mov dx,joyport                     ; joyport address
  136.          xor al,al
  137.          out dx,al
  138.  
  139.          mov ecx,0                          ; reset timer
  140.          align 4
  141.  
  142. joyloop:
  143.          in al,dx                           ; get bits from port
  144.  
  145.          test al,1                          ; timer bit set?
  146.          jnz s notax
  147.          test _joy_tax,-1                   ; value already got?
  148.          jnz s notax
  149.          mov _joy_tax,ecx                   ; set axis value
  150.          dec bl                             ; port is in, flag one less waiting
  151.          jz found_joyval                    ; all ports are in, exit
  152. notax:
  153.          test al,2
  154.          jnz s notay
  155.          test _joy_tay,-1
  156.          jnz s notay
  157.          mov _joy_tay,ecx
  158.          dec bl
  159.          jz found_joyval                    ; all ports are in, exit
  160. notay:
  161.          test al,4
  162.          jnz s notbx
  163.          test _joy_tbx,-1
  164.          jnz s notbx
  165.          mov _joy_tbx,ecx
  166.          dec bl
  167.          jz found_joyval                    ; all ports are in, exit
  168. notbx:
  169.          test al,8
  170.          jnz s notby
  171.          test _joy_tby,-1
  172.          jnz s notby
  173.          mov _joy_tby,ecx
  174.          dec bl
  175.          jz found_joyval                    ; all ports are in, exit
  176. notby:
  177.          inc ecx
  178.          cmp ecx,time_out                   ; abort if ports fail to arrive in time
  179.          jng joyloop
  180.  
  181. found_joyval:
  182.          sti
  183.          mov eax,_joy_tax                   ; -1 = port inactive
  184.          mov ebx,_joy_tay
  185.          mov ecx,_joy_tbx
  186.          mov edx,_joy_tby
  187.  
  188.          ret
  189.  
  190. ;░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░
  191. ; Justgetbutton:  Get button status
  192. ; In:none
  193. ; Out:
  194. ;   AL - Current button status
  195. ;   DL - Button changed status
  196. ;
  197. ;  7  B  button 2 - 0 = button up,1 = button down
  198. ;  6  B  button 1 - 0 = button up,1 = button down
  199. ;  5  A  button 2 - 0 = button up,1 = button down
  200. ;  4  A  button 1 - 0 = button up,1 = button down
  201. ;  3  B  button 2 - 1 = button up,0 = button down
  202. ;  2  B  button 1 - 1 = button up,0 = button down
  203. ;  1  A  button 2 - 1 = button up,0 = button down
  204. ;  0  A  button 1 - 1 = button up,0 = button down
  205. ;░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░
  206.  
  207. _joy_justgetbutton: ; get present button status
  208.          mov al,_joy_thiscallstate          ; save button state for next call
  209.          mov _joy_lastcallstate,al
  210.          mov dx, joyport                    ; port address of game adapter
  211.          in al, dx                          ; al = game port state
  212.          and al, 0f0h                       ; lose lower nibble
  213.          mov dh, al                         ; 0f = button down mask
  214.          shr al, 4                          ; shift mask to lower nibble
  215.          or al, dh                          ; al = combined button event mask
  216.          xor al, 0f0h                       ; f0 = button up mask
  217.          xor ah, ah                         ; zero out ah for return
  218.          mov _joy_thiscallstate, al         ; al = current button status
  219.          mov dx,ax
  220.          xor dl,_joy_lastcallstate          ; dl = button changed status
  221.          ret
  222.  
  223. ;░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░
  224. ; Calibrate_Joystick: Initial joystick grab
  225. ; In=Out=null
  226. ; Notes:
  227. ;  Joystick values are grabbed on entry and calibrated as if  the joystick was
  228. ;  at the center when called.  The joystick re-calculation will not be correct
  229. ;  if the user enters the program with the joystick at non-center, or  if  the
  230. ;  the user turns the turbo off/on while the program is running.
  231. ;
  232. ; The joystick buttons must be in an off state before the routine will continue
  233. ; It does not HAVE to be off, I just do this so that the user will know if  the
  234. ; joystick is stuck up against the monitor or crushed under some books.
  235. ;░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░
  236.  
  237. _joy_calibratejoystick:
  238.          call _joy_waitalloff               ; wait until button released before entering
  239.  
  240.          mov _joy_tax,0                     ; clear joystick flags
  241.          mov _joy_tay,0
  242.          mov _joy_tbx,0
  243.          mov _joy_tby,0
  244.          call _joy_rawjoystick              ; get first values
  245.          sub _joy_tax,1                     ; 0 becomes -1
  246.          sub _joy_tay,1                     ; >0 becomes >=0
  247.          sub _joy_tbx,1
  248.          sub _joy_tby,1
  249.          call _joy_rawjoystick              ; get new values, -1's are inactive ports
  250.  
  251.          cmp _joy_tax,-1                    ; test if joystick A valid
  252.          je cal_noa
  253.  
  254.          mov eax,_joy_tax                   ; hopefully we have joystick A center
  255.          mov ebx,_joy_tay
  256.          mov _joycenax,eax                  ; save center of joystick
  257.          mov _joycenay,ebx
  258. cal_noa:
  259.          cmp _joy_tbx,-1                    ; test if joystick B valid
  260.          je cal_nob
  261.  
  262.          mov eax,_joy_tbx                   ; hopefully we have joystick B center
  263.          mov ebx,_joy_tby
  264.          mov _joycenbx,eax                  ; save center of joystick
  265.          mov _joycenby,ebx
  266. cal_nob:
  267.          ret
  268.  
  269. ;░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░
  270. ; _joy_cartisianjoystick: Get joystick values in cartisian format.
  271. ; In:
  272. ;   _joycenax - joystick centers, raw data
  273. ;   _joycenay -
  274. ;   _joycenbx -
  275. ;   _joycenby -
  276. ; Out:
  277. ; _joy_ax = EAX = x of joystick a (-16384 to 16384)
  278. ; _joy_ay = EBX = y of joystick a
  279. ; _joy_bx = ECX = x of joystick b
  280. ; _joy_by = EDX = y of joystick b
  281. ;
  282. ; Notes:
  283. ; Assuming calibration routine was entered with  the  joystick  in  the  center
  284. ; position, this routine should be machine independant.
  285. ;
  286. ; The dead_zone is the zone on any axis which the joystick center is registered
  287. ; as  being zero.  This  prevents  the  joystick  from  jittering  when  it  is
  288. ; positioned in the center without anyone touching it.  The  dead_zone  can  be
  289. ; set to a high value when selecting menu items and this will produce a  yes/no
  290. ; response from the joystick.  The zone can then be set back down low  for  the
  291. ; game/demo.
  292. ;
  293. ; The resulting position should be from -16384 to +16384.   But  it  could  be
  294. ; outside this limit if the joystick is not centered correctly  (as  the  real
  295. ; world rarely is centered)
  296. ;░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░
  297.  
  298. _joy_cartisianjoystick:
  299.          call _joy_rawjoystick              ; get joystick values
  300.  
  301.          mov esi,_joy_deadzone
  302.          push edx
  303.  
  304.          cmp eax,-1                         ; test if joystick A valid
  305.          je car_noa
  306.  
  307.          sub eax,_joycenax                  ; convert to cartisian
  308.          sub ebx,_joycenay
  309.  
  310.          shl eax,14                         ; get ready for divide
  311.          shl ebx,14
  312.  
  313.          cdq
  314.          mov ebp,_joycenax
  315.          idiv ebp
  316.  
  317.          cmp eax,esi
  318.          jl car_ca
  319.          sub eax,esi
  320.          jmp car_cc
  321. car_ca:
  322.          neg eax
  323.          cmp eax,esi
  324.          jl car_cb
  325.          neg eax
  326.          add eax,esi
  327.          jmp car_cc
  328. car_cb:
  329.          xor eax,eax
  330. car_cc:
  331.          mov _joy_ax,eax
  332.  
  333.          mov eax,ebx
  334.          cdq
  335.          mov ebp,_joycenay
  336.          idiv ebp
  337.  
  338.          cmp eax,esi
  339.          jl car_cz
  340.          sub eax,esi
  341.          jmp car_ce
  342. car_cz:
  343.          neg eax
  344.          cmp eax,esi
  345.          jl car_cd
  346.          neg eax
  347.          add eax,esi
  348.          jmp car_ce
  349. car_cd:
  350.          xor eax,eax                        ; in dead_zone, eax=0
  351. car_ce:
  352.          mov _joy_ay,eax
  353. car_noa:
  354.          pop eax                            ; y co-ordinate of joy B
  355.  
  356.          cmp ecx,-1                         ; test if joystick B valid
  357.          je car_nob
  358.  
  359.          sub eax,_joycenbx                  ; convert to cartisian
  360.          sub ecx,_joycenby
  361.  
  362.          shl eax,14                         ; get ready for divide
  363.          shl ecx,14
  364.  
  365.          cdq
  366.          mov ebp,_joycenbx
  367.          idiv ebp
  368.  
  369.          cmp eax,esi
  370.          jl car_cf
  371.          sub eax,esi
  372.          jmp car_ch
  373. car_cf:
  374.          neg eax
  375.          cmp eax,esi
  376.          jl car_cg
  377.          neg eax
  378.          add eax,esi
  379.          jmp car_ch
  380. car_cg:
  381.          xor eax,eax
  382. car_ch:
  383.          mov _joy_by,eax
  384.  
  385.          mov eax,ecx
  386.          cdq
  387.          mov ebp,_joycenby
  388.          idiv ebp
  389.  
  390.          cmp eax,esi
  391.          jl car_ci
  392.          sub eax,esi
  393.          jmp car_ck
  394. car_ci:
  395.          neg eax
  396.          cmp eax,esi
  397.          jl car_cj
  398.          neg eax
  399.          add eax,esi
  400.          jmp car_ck
  401. car_cj:
  402.          xor eax,eax                        ; in dead_zone, eax=0
  403. car_ck:
  404.          mov _joy_bx,eax
  405. car_nob:
  406.          mov eax,_joy_ax
  407.          mov ebx,_joy_ay
  408.          mov ecx,_joy_bx
  409.          mov edx,_joy_by
  410.  
  411.          ret
  412.  
  413. ;░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░
  414. ; Wait_all_off: wait for all buttons to return to 0 - abort if ESC pressed
  415. ;░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░░
  416.  
  417. _joy_waitalloff:
  418.          mov ecx,15                         ; wait must be performed 15 times in case buttons are rusty (like mine...)
  419.  
  420. wait_all_off2:
  421.          push ecx
  422.  
  423. wait_all_off3:
  424.          call _joy_justgetbutton
  425.          mov cl,al
  426.          in al,60h                          ; esc pressed on keyboard aborts wait.
  427.          cmp al, 1
  428.          je wait_all_off4
  429.          test cl,3*16                       ; test any button
  430.          jnz wait_all_off3                  ; button up, try again
  431.  
  432. wait_all_off4:
  433.          pop ecx                            ; button down, make sure it is really down
  434.          loop wait_all_off2
  435.  
  436.          ret
  437.  
  438. code32   ends
  439.          end
  440.